package edu.scau.mis.sys.security.service;

import edu.scau.mis.core.redis.RedisCache;
import edu.scau.mis.sys.entity.SysRole;
import edu.scau.mis.sys.entity.SysAdmin;
import edu.scau.mis.sys.security.domain.LoginUser;
import edu.scau.mis.sys.service.SysAdminService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * Authentication用户认证服务类
 */
@Service("userDetailsServiceImpl")
public class UserDetailsServiceImpl implements UserDetailsService {
    @Autowired
    SysAdminService sysAdminService;

    @Autowired
    RedisCache redisCache;

    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {

        List<GrantedAuthority> authorities = new ArrayList<>();
        GrantedAuthority authority;
        SysAdmin sysAdmin = sysAdminService.queryByUsername(username);

        // 是否找到用户，未找到抛出异常
        if (sysAdmin == null) {
            throw new UsernameNotFoundException("未找到用户");
        }

        List<SysRole> roles = sysAdmin.getRoles();
        // 是否获得权限集合
        if(roles != null){
            for(SysRole role : roles){
                authority = new SimpleGrantedAuthority(role.getCode());
                authorities.add(authority);
            }
        }

        // redis中存储loginUser，为简化暂时使用username为key
        String userKey = sysAdmin.getUsername();

        // redis中存储loginUser
        long loginTime = System.currentTimeMillis(); //登录时间
        int addExpireTime = 30 * 60 * 1000; //设置loginUser的缓存过期时间为30分钟。建议与token过期时间相等或者小于token过期时间。
        long expireTime = loginTime + addExpireTime; //过期时间

        LoginUser loginUser = new LoginUser(sysAdmin.getId(), sysAdmin.getUsername(), sysAdmin.getPassword(), sysAdmin, loginTime, expireTime, authorities);

        // 调用工具类存储login对象
        redisCache.setCacheObject(userKey, loginUser, addExpireTime, TimeUnit.MINUTES);

        // 创建登录用户对象进行验证
        return loginUser;
    }
}